package com.learn.demo.nio;

import java.io.IOException;
import java.net.InetSocketAddress;
import java.net.SocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.SelectionKey;
import java.nio.channels.Selector;
import java.nio.channels.SocketChannel;
import java.util.Iterator;
import java.util.Scanner;
import java.util.Set;

public class NIOGroupDemoClient {
    private static final String IP_ADDRESS = "127.0.0.1";
    private static final int PORT = 8888;
    private static Selector selector;
    private static SocketChannel socketChannel;

    public NIOGroupDemoClient() {
        try {
            socketChannel = SocketChannel.open(new InetSocketAddress(IP_ADDRESS, PORT));
            socketChannel.configureBlocking(false);
            selector = Selector.open();
            socketChannel.register(selector, SelectionKey.OP_READ);
            System.out.println("客户端启动:" + socketChannel.getLocalAddress());
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public void sendInfo(String msg) {
        try {
            SocketAddress localAddress = socketChannel.getLocalAddress();
            socketChannel.write(ByteBuffer.wrap((localAddress + "说：" + msg).getBytes()));
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    public void readInfo() throws IOException {
        int selectCount = selector.select();
        if (selectCount > 0) {
            Set<SelectionKey> selectionKeys = selector.selectedKeys();
            Iterator<SelectionKey> selectionKeyIterator = selectionKeys.iterator();
            while (selectionKeyIterator.hasNext()) {
                SelectionKey selectionKey = selectionKeyIterator.next();
                if (selectionKey.isReadable()) {
                    try {
                        SocketChannel socketChannel = (SocketChannel) selectionKey.channel();
                        socketChannel.configureBlocking(false);
                        ByteBuffer byteBuffer = ByteBuffer.allocate(1024);
                        int readCount = socketChannel.read(byteBuffer);
                        if (readCount > 0) {
                            System.out.println(new String(byteBuffer.array()));
                        }
                    } catch (Exception e) {
                        try {
                            selectionKey.cancel();
                            selector.close();
                            socketChannel.close();
                        } catch (IOException ioException) {
                            ioException.printStackTrace();
                        }
                        System.out.println("服务器断开连接");
                        System.exit(-1);
                    }

                }
            }
            selectionKeyIterator.remove();
        }
    }

    public static void main(String[] args) {
        NIOGroupDemoClient client = new NIOGroupDemoClient();
        new Thread(() -> {
            while (true) {
                try {
                    client.readInfo();
                } catch (Exception e) {
                    e.printStackTrace();
                    break;
                }

            }
        }).start();
        Scanner scanner = new Scanner(System.in);
        while (scanner.hasNextLine()) {
            String msg = scanner.nextLine();
            client.sendInfo(msg);
        }
    }
}
